package com.lemon.exam.controller;

import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import jakarta.annotation.security.DenyAll;
import jakarta.annotation.security.PermitAll;
import org.springframework.security.access.prepost.PostAuthorize;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.security.access.prepost.PreFilter;
import org.springframework.web.bind.annotation.*;
import reactor.core.publisher.Flux;
import reactor.core.publisher.Mono;

/**
 * 测试接口，测试用，没有实际业务需求
 *
 * @author Lemon
 * @since 2025/10/31 10:52
 */
@RestController
@RequestMapping("test")
@Tag(name = "测试接口", description = "没有实际业务需求")
public class TestController {
    /**
     * 测试 @PermitAll
     * 指示一个特定的类或方法可以被任何用户访问
     *
     * @return
     */
    @GetMapping("test01")
    @Operation(summary = "测试 @PermitAll", description = "指示一个特定的类或方法可以被任何用户访问")
    @PermitAll
    public Mono<String> test01() {
        return Mono.just("test01");
    }

    /**
     * 测试 @DenyAll
     * 指示一个特定的类或方法不能被任何用户访问
     *
     * @return
     */
    @GetMapping("test02")
    @Operation(summary = "测试 @DenyAll", description = "指示一个特定的类或方法不能被任何用户访问")
    @DenyAll
    public Mono<String> test02() {
        return Mono.just("test02");
    }

    /**
     * 测试 @PreAuthorize
     * 在方法调用前验证用户权限
     *
     * @return
     */
    @GetMapping("test03")
    @Operation(summary = "测试 @PreAuthorize", description = "在方法调用前验证用户权限")
    //@PreAuthorize("hasAuthority('ROLE_admin')")
    //@PreAuthorize("hasAuthority('ROLE_teacher')")
    //@PreAuthorize("hasAuthority('ROLE_student')")
    @PreAuthorize("hasAuthority('sys:test03')")
    //@PreAuthorize("hasAuthority('sys:home:getCurrentUser')")
    //@PreAuthorize("hasAnyAuthority('ROLE_admin','ROLE_student')")
    //@PreAuthorize("hasAnyAuthority('ROLE_admin','ROLE_teacher')")
    //@PreAuthorize("hasAnyAuthority('sys:home:getCurrentUser','sys:test03')")
    public Mono<String> test03() {
        return Mono.just("test03");
    }

    /**
     * 测试 @PreAuthorize
     * 在方法调用前验证用户权限
     *
     * @return
     */
    @GetMapping("test04")
    @Operation(summary = "测试 @PreAuthorize", description = "在方法调用前验证用户权限")
    @PreAuthorize("hasRole('ROLE_admin')")
    //@PreAuthorize("hasRole('ROLE_teacher')")
    //@PreAuthorize("hasRole('ROLE_student')")
    //@PreAuthorize("hasAnyRole('ROLE_admin')")
    //@PreAuthorize("hasAnyRole('ROLE_teacher')")
    //@PreAuthorize("hasAnyRole('ROLE_student')")
    public Mono<String> test04() {
        return Mono.just("test04");
    }

    /**
     * 测试 @PreAuthorize
     * 在方法调用前验证用户权限
     * 自定义权限规则，需要自定义权限处理器 PermissionEvaluatorHandler，目前默认 return true
     *
     * @return
     */
    @GetMapping("test05")
    @Operation(summary = "测试 @PreAuthorize", description = "在方法调用前验证用户权限")
    //@PreAuthorize("hasPermission('test05')")
    @PreAuthorize("hasPermission('/home/getCurrentUser','/user/getById/{id}')")
    public Mono<String> test05() {
        return Mono.just("test05");
    }

    /**
     * 测试 @PreFilter
     * 在方法执行前对参数或返回值进行过滤
     *
     * @return
     */
    @PostMapping("test06")
    @Operation(summary = "@PreFilter", description = "在方法执行前对参数或返回值进行过滤")
    @PreFilter(filterTarget = "ids", value = "filterObject > 4")
    public Mono<String> test06(@RequestBody Flux<Integer> ids) {
        return ids.collectList().map(list -> "test06" + list);
    }

    /**
     * 测试 @PostAuthorize
     * 用于在方法执行后进行权限校验
     *
     * @return
     */
    @GetMapping("test07")
    @Operation(summary = "@PostAuthorize", description = "用于在方法执行后进行权限校验")
    //@PostAuthorize("hasAuthority('ROLE_admin')")
    @PostAuthorize("hasAuthority('ROLE_student')")
    public Mono<String> test07() {
        return Mono.just("test07");
    }

}
